package com.tarena.lbs.basic.web.service;

import com.alibaba.nacos.common.utils.CollectionUtils;
import com.github.pagehelper.PageInfo;
import com.tarena.lbs.base.common.utils.Asserts;
import com.tarena.lbs.base.protocol.exception.BusinessException;
import com.tarena.lbs.base.protocol.pager.PageResult;
import com.tarena.lbs.basic.web.repository.AdminRepository;
import com.tarena.lbs.basic.web.repository.UserGroupRepository;
import com.tarena.lbs.basic.web.repository.UserTagsRepository;
import com.tarena.lbs.common.passport.principle.UserPrinciple;
import com.tarena.lbs.common.security.utils.LbsSecurityContenxt;
import com.tarena.lbs.pojo.basic.param.UserGroupParam;
import com.tarena.lbs.pojo.basic.po.AdminPO;
import com.tarena.lbs.pojo.basic.po.UserGroupPO;
import com.tarena.lbs.pojo.basic.po.UserTagsPO;
import com.tarena.lbs.pojo.basic.query.UserGroupQuery;
import com.tarena.lbs.pojo.basic.vo.UserGroupVO;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

@Service
public class UserGroupService {
    @Autowired
    private AdminRepository adminRepository;
    @Autowired
    private UserGroupRepository userGroupRepository;
    @Autowired
    private UserTagsRepository userTagsRepository;
    //DAY11-PM  02、后台查询用户人群数据的分页列表
    public PageResult<UserGroupVO> userGroupPage(UserGroupQuery query) throws BusinessException {
        //1.解析认证对象 利用id值 查询登录用AdminPO详情 包含businessId
        UserPrinciple userPrinciple = LbsSecurityContenxt.getLoginToken();
        Asserts.isTrue(userPrinciple==null,new BusinessException("-2","用户认证解析失败"));
        //1.1 无法解析认证异常 1.2 查不到adminPO
        AdminPO adminPO=adminRepository.getAdminById(userPrinciple.getId());
        Asserts.isTrue(adminPO==null,new BusinessException("-2","商家信息不存在"));
        Integer businessId=adminPO.getBusinessId();
        //2 调用仓储层查询分页
        PageInfo<UserGroupPO> pageInfo=userGroupRepository.getUserGroups(query,businessId);
        //3.组织封装分页的vo返回
        // 创建一个分页结果对象，用于封装用户组的分页数据
        PageResult<UserGroupVO> voPage=new PageResult<>();
        // 设置当前页码
        voPage.setPageNo(pageInfo.getPageNum());
        // 设置页面大小
        voPage.setPageSize(pageInfo.getPageSize());
        // 设置总记录数
        voPage.setTotal(pageInfo.getTotal());
        // 定义用户组的VO列表，暂时置为nul
        List<UserGroupVO> vos=null;
        if(CollectionUtils.isNotEmpty(pageInfo.getList())){
            vos=pageInfo.getList().stream().map(po->{
                UserGroupVO vo=new UserGroupVO();
                BeanUtils.copyProperties(po,vo);
                return vo;
            }).collect(Collectors.toList());
        }
        voPage.setObjects(vos);
        return voPage;
    }

    public void userGroupSave(UserGroupParam param) throws BusinessException {
        //1.解析认证对象 利用id值 查询登录用AdminPO详情 包含businessId
        UserPrinciple userPrinciple = LbsSecurityContenxt.getLoginToken();
        Asserts.isTrue(userPrinciple==null,new BusinessException("-2","用户认证解析失败"));
        //1.1 无法解析认证异常 1.2 查不到adminPO
        AdminPO adminPO=adminRepository.getAdminById(userPrinciple.getId());
        Asserts.isTrue(adminPO==null,new BusinessException("-2","商家信息不存在"));
        Integer businessId = adminPO.getBusinessId();
        //2、先查询当前名字 groupName 当晚商家businessId是否存在人群;
         Long total = userGroupRepository.countUserGroupByNameAndBizId(param.getGroupName(),businessId);
         Asserts.isTrue(total>0,new BusinessException("-2","人群已经存在"));
         //3、封装po 写入数据库表格
        UserGroupPO poParam = new UserGroupPO();
        BeanUtils.copyProperties(param,poParam);
        poParam.setBusinessId(businessId);
        poParam.setCreateAt(new Date());
        userGroupRepository.saveUserGroup(poParam);
    }

    //根据用户ID获取用户组ID列表
    public List<Integer> getUserGroupIds(Integer userId) {
        //分析实体数据关系 通过标签表格 做人群查询
        //方案1: 先查标签 在查人群
        //方案2: 复杂sql关联查询 select lbs_user_group.id from a left join...
        //对应用户 2c的业务 尽可能不使用复杂sql 原因是 负责sql会锁表
        //select * from lbs_user_tags where user_id=#{userId} 返回一个 userTagsPOList 3,31
        List<UserTagsPO> pos=userTagsRepository.getUserTagsByUserId(userId);   // 通过用户ID查询用户标签
        // 提取查询到的用户标签中的标签ID
        List<Integer> userTagIds=pos.stream().map(po->{return po.getTagId();}).collect(Collectors.toList());
        //就将 所有用户人群 查询出来 解析tagIds
        //select * from lbs_user_group where FIND_IN_SET(3,tag_ids) or FIND_IN_SET(31,tag_ids)
        // 根据用户标签ID列表查询相关的用户群组
        List<UserGroupPO> groupPos=userGroupRepository.getUserGroupsByTagIds(userTagIds);
        // 定义一个用于存储群组ID的列表
        List<Integer> groupIds=null;
        // 如果查询到的群组列表不为空
        if(CollectionUtils.isNotEmpty(groupPos)){
            // 从群组列表中提取出群组ID，并收集到一个新的列表中
            groupIds=groupPos.stream().map(po->{return po.getId();}).collect(Collectors.toList());
        }
        return groupIds;
    }
}
